package net.http;

import com.google.gson.Gson;
import com.google.gson.GsonBuilder;

import net.client.HttpClient;

import java.util.Map;

import retrofit2.Retrofit;
import retrofit2.adapter.rxjava2.RxJava2CallAdapterFactory;
import retrofit2.converter.gson.GsonConverterFactory;
import retrofit2.converter.scalars.ScalarsConverterFactory;

public class HttpManager {
    private static Retrofit retrofit;
    private static HttpManager mInstance = null;
    private Retrofit.Builder rbuilder;
    public  String baseUrl = "https://www.wanandroid.com";//测试
    private HttpClient mHttpClient = null;
    private int mTimeOut = 60;  //默认时间
    private String mCacheFile = null;    //默认没有缓存
    private boolean mEnableLog = true;   //默认打印日志
    private Map<String, String> mHeadMap = null;
    /**
     * 设置请求头的baseurl的key值
     */
    public final static String BASE_URL_KEY = "baseurl_key_name";

    /**
     * 1.初始化 HttpClient creatHttpClient()默认了参数
     * 2.创建 Retrofit.Builder
     */
    private HttpManager() {
        mHttpClient = creatHttpClient();
        rbuilder = getRbuilder();
    }

    /**
     * 获取本类的一个实例对象，使用DCC的模式设计单俐
     *
     *
     *
     * @return 单例
     */
    public static HttpManager getInstance() {
        if (mInstance == null) {
            synchronized (HttpManager.class) {
                if (mInstance == null) {
                    mInstance = new HttpManager();
                }
            }
        }
        return mInstance;
    }

    public static BaseRequest get(){
        return new BaseRequest();
    }
    public String getBaseUrl(){
        return baseUrl;
    }
    /**
     * 初始化一些操作对象，包括retrofit和httpClient
     * 这个方法一般在应用的入口处值调用一次即可，不用多次调用
     */
    public void init() {
        buildHttpClient();
        rbuilder .baseUrl(baseUrl)
                //如果请求返回的不是json 而是字符串，则使用下面的解析器
                .addConverterFactory(ScalarsConverterFactory.create())
                //如果请求返回额是json则使用下面的解析器，
                //注意：这两句的顺序不能对调，否则不能同时兼容字符串和json
                .addConverterFactory(GsonConverterFactory.create(buildGson()))
                //添加Rxjava的支持，把Retrofit转成Rxjava可用的适配类
                .addCallAdapterFactory(RxJava2CallAdapterFactory.create())
                .client(mHttpClient.buildClient());
        retrofit = rbuilder.build();
    }

    public Retrofit.Builder getRbuilder(){
        return new Retrofit.Builder();
    }
    public Retrofit getRetrofit() {
        return retrofit;
    }

    /**
     * 创建httpClient
     */
    private HttpClient creatHttpClient() {
        return new HttpClient();
    }

    /**
     * 设置默认的参数
     */
    private void buildHttpClient(){
        mHttpClient.setTimeOut(mTimeOut);
        mHttpClient.setCacheDir(mCacheFile);
        mHttpClient.setHeadMap(mHeadMap);
        mHttpClient.enableLog(mEnableLog);
    }


    public Gson buildGson() {
        return new GsonBuilder().setLenient()// json宽松
                .enableComplexMapKeySerialization()//支持Map的key为复杂对象的形式
                .serializeNulls() //智能null,支持输出值为null的属性
                .setPrettyPrinting()//格式化输出（序列化）
                .create();
    }

    /**
     * 设置全局 baseUrl
     * @param url
     * @return
     */
    public HttpManager setBaseUrl(String url) {
        baseUrl = url;
        return this;
    }
    /**
     * 设置http请求的缓存文件路劲，默认为空，可以不用设置。
     *
     * @param filePath
     * @return
     */
    public HttpManager setCacheFile(String filePath) {
        mCacheFile = filePath;

        return this;
    }


    /**
     * 是否开启日志
     *
     * @param enable
     * @return
     */
    public HttpManager enableLog(boolean enable) {

        mEnableLog = enable;

        return this;
    }

    /**
     * 设置请求超时时间
     *
     * @param time
     * @return
     */
    public HttpManager setTimeOut(int time) {
        mTimeOut = time;
        return this;
    }

    /**
     * 设置附加的头信息，key为头名称，value为对应的值，默认已经设置了请求
     * 所需要的基本头，如果还需要额外的请求头，则可以通过这个方法进行设置
     *
     * @param head
     * @return
     */
    public HttpManager setHeadMap(Map<String, String> head) {
        mHeadMap = head;
        return this;
    }

    public HttpClient getmHttpClient(){
        return this.mHttpClient;
    }
}
